home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Cream of the Crop 22
/
Cream of the Crop 22.iso
/
doom
/
quake2.zip
/
MDL23DS.ZIP
/
3DS.C
next >
Wrap
C/C++ Source or Header
|
1996-08-20
|
5KB
|
211 lines
// move fp to end of chunk after ALL chunk writes
#include "3ds.h"
#define MAGIC 0x4D4D
#define VERSION 0x0002
#define MESH 0x3D3D
#define OBJECT 0x4000
#define HIDDEN 0x4010
#define TRIOBJ 0x4100
#define VERTS 0x4110
#define FACES 0x4120
#define TVERTS 0x4140
dword start_chunk ( FILE *fp, word chunk_id );
word end_chunk ( FILE *fp, dword location );
word write_ver ( FILE *fp, dword ver );
word write_mesh ( FILE *fp, mdl_object *obj );
word write_object ( FILE *fp, mdl_object *obj, dword findex );
word write_triobj ( FILE *fp, mdl_object *obj, dword findex );
word write_verts ( FILE *fp, mdl_object *obj, dword findex );
word write_faces ( FILE *fp, mdl_object *obj ); // obj only have one set
word write_tverts ( FILE *fp, mdl_object *obj ); // only one set
dword start_chunk ( FILE *fp, word chunk_id ) {
dword location;
location = ftell(fp);
fwrite(&chunk_id,2,1,fp);
fseek(fp,4,SEEK_CUR); // skip length
return location; }
word end_chunk ( FILE *fp, dword location ) {
dword length;
length = ftell(fp)-location; // current - start
fseek(fp,location+2,SEEK_SET);
fwrite(&length,4,1,fp);
fseek(fp,length-6,SEEK_CUR); // to end of chunk
return 0; }
word write_3ds ( mdl_object *obj, byte *filename ) {
dword location;
FILE *fp;
fp = fopen ( filename, "wb" );
if ( !fp ) {
printf("unable to open .3ds file \"%s\"\n",filename);
exit(1);
}
location = start_chunk ( fp, MAGIC );
// write all data below
write_ver ( fp, 3 );
write_mesh ( fp, obj );
// write length
end_chunk ( fp, location );
fclose(fp);
return 0; }
word write_ver ( FILE *fp, dword ver ) {
dword location;
location = start_chunk ( fp, VERSION );
fwrite(&ver,4,1,fp);
end_chunk ( fp, location );
return 0; }
word write_mesh ( FILE *fp, mdl_object *obj ) {
dword location;
word findex; // frame index
location = start_chunk ( fp, MESH );
// install loop here to write all frames
for ( findex=0; findex< obj->head.frame_num; findex++ ) {
write_object ( fp, obj, findex );
printf("wrote frame %u\n",findex);
} // end for
end_chunk ( fp, location );
return 0; }
word write_object ( FILE *fp, mdl_object *obj, dword findex ) {
dword location;
dword index;
location = start_chunk ( fp, OBJECT );
// write name
index=0;
do {
fwrite(&obj->frame_ptr[findex].name[index],1,1,fp);
index++;
} while ( obj->frame_ptr[findex].name[index-1] && ( index < 256 ) );
// write data
write_triobj ( fp, obj, findex );
end_chunk ( fp, location );
return 0; }
word write_triobj ( FILE *fp, mdl_object *obj, dword findex ) {
dword location;
location = start_chunk ( fp, TRIOBJ );
write_verts ( fp, obj, findex );
write_tverts ( fp, obj );
write_faces ( fp, obj ); // no frame index needed
end_chunk ( fp, location );
return 0; }
word write_verts ( FILE *fp, mdl_object *obj, dword findex ) {
dword location;
float x,y,z;
word vert_num;
word v0;
location = start_chunk ( fp, VERTS );
//
vert_num = obj->head.vert_num;
fwrite(&vert_num,2,1,fp);
for ( v0=0; v0< vert_num; v0++ ) {
x = obj->frame_ptr[findex].vert_ptr[v0].x *
obj->head.scale.x + obj->head.origin.x + obj->head.eye_pos.x;
y = obj->frame_ptr[findex].vert_ptr[v0].y *
obj->head.scale.y + obj->head.origin.y + obj->head.eye_pos.y;
z = obj->frame_ptr[findex].vert_ptr[v0].z *
obj->head.scale.z + obj->head.origin.z + obj->head.eye_pos.z;
fwrite(&y,4,1,fp);
x = -x;
fwrite(&x,4,1,fp);
fwrite(&z,4,1,fp);
} // end v0
end_chunk ( fp, location );
return 0; }
word write_faces ( FILE *fp, mdl_object *obj ) {
dword location;
word face_num;
word v0,v1,v2;
word flags = 1030; // not sure what this represents
word f0;
location = start_chunk ( fp, FACES );
face_num = obj->head.tri_num;
fwrite(&face_num,2,1,fp);
//printf("writing %u faces\n",face_num );
for ( f0=0; f0< face_num; f0++ ) {
v2 = obj->tri_ptr[f0].vert[0]; // v0 swapped for v2 ( normal fix )
v1 = obj->tri_ptr[f0].vert[1];
v0 = obj->tri_ptr[f0].vert[2];
fwrite(&v0,2,1,fp);
fwrite(&v1,2,1,fp);
fwrite(&v2,2,1,fp);
fwrite(&flags,2,1,fp);
//printf("wrote face %u %u %u - %u\n",v0,v1,v2,flags);
} // end f0
end_chunk ( fp, location );
return 0; }
word write_tverts ( FILE *fp, mdl_object *obj ) {
dword location;
word tvert_num;
word t0;
float u,v;
location = start_chunk ( fp, TVERTS );
tvert_num = obj->head.vert_num;
fwrite(&tvert_num,2,1,fp);
//printf("writing %u tverts\n",tvert_num);
for ( t0=0; t0< tvert_num; t0++ ) {
u = obj->tvert_ptr[t0].s;
if ( u > (obj->head.skin_width/2) ) // back to one side
u -= (obj->head.skin_width/2);
u /= obj->head.skin_width;
v = obj->tvert_ptr[t0].t;
// flip here for proper texmaps
v -= obj->head.skin_height/2;
v = -v;
v += obj->head.skin_height/2;
// flip done
v /= obj->head.skin_height;
fwrite(&u,4,1,fp);
fwrite(&v,4,1,fp);
//printf("tvert %u: %8.2f %8.2f\n",t0,u,v);
} // end t0
end_chunk ( fp, location );
return 0; }